package org.jeecg.modules.health_records.files_upload;

import io.swagger.annotations.Api;
import io.swagger.annotations.ApiOperation;
import org.apache.shiro.SecurityUtils;
import org.jeecg.common.api.vo.Result;
import org.jeecg.common.system.vo.LoginUser;
import org.jeecg.common.util.oConvertUtils;
import org.jeecg.modules.health_records.pic_path.entity.PicPathInfo;
import org.jeecg.modules.health_records.pic_path.service.IPicPathInfoService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.web.bind.annotation.*;
import org.springframework.web.multipart.MultipartFile;

import javax.servlet.http.HttpServletResponse;
import java.io.*;
import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.util.Date;
import java.util.List;
import java.util.zip.ZipEntry;
import java.util.zip.ZipOutputStream;

@RestController
@RequestMapping("/file")
@Api(tags = "文件上传下载")
public class FileController {
  //存储路径
    @Value("${jeecg.path.upload}")
    private String uploadPath;
  //访问路径
    @Value("${jeecg.path.access-path}")
    private String accessPath;
    //访问路径
    @Value("${jeecg.path.static-path}")
    private String staticPath;
    @Value("${jeecg.path.allowed-extensions}")
    private String allowedExtensions;

    @Autowired
    private IPicPathInfoService picPathInfoService;
    private static final SimpleDateFormat sdf = new SimpleDateFormat("yyyyMMdd");

  /*  @PostMapping("/uploadImage")
    @ApiOperation("图片上传接口")
    public Result<String> uploadImage(@RequestParam("file") MultipartFile file) {
        Result<String> result = new Result<>();
        try {
            // 上传图片文件
            String relativePath = FileUploadUtil.uploadImage(file, uploadPath, allowedExtensions);

            // 构建访问URL
            String accessUrl = accessPath + relativePath.replace("\\", "/");

            result.setResult(accessUrl);
            result.setSuccess(true);
            result.setMessage("上传成功");
        } catch (IllegalArgumentException e) {
            result.setSuccess(false);
            result.setMessage(e.getMessage());
        } catch (Exception e) {
            result.setSuccess(false);
            result.setMessage("上传失败: " + e.getMessage());
            e.printStackTrace();
        }
        return result;
    }*/

    @PostMapping("/batchUploadImage")
    @ApiOperation(value="批量上传图片并关联业务",notes="输入参数：必传文件组对象files，必传关联的业务所在的表id-businessId，选传业务类型businessType")
    public Result<List<String>> batchUploadImage(
            @RequestParam("files") MultipartFile[] files,
            @RequestParam String businessId,
            @RequestParam String businessType) {

        Result<List<String>> result = new Result<>();
        LoginUser loginUser = (LoginUser) SecurityUtils.getSubject().getPrincipal();
        String createBy = loginUser != null ? loginUser.getUsername() : "system";

        if (files == null || files.length == 0) {
            result.setSuccess(false);
            result.setMessage("请选择要上传的图片");
            return result;
        }

        List<String> imagePaths = new ArrayList<>();
        List<String> errorMessages = new ArrayList<>();
        // 按日期生成目录
        String dateDir = sdf.format(new Date());
        String savePath = uploadPath + File.separator + dateDir + File.separator;

        int i =1; //用于图片排序
        for (MultipartFile file : files) {
            try {
                // 上传图片文件
                String relativePath = FileUploadUtil.uploadImage(file, uploadPath, allowedExtensions);
                // 构建访问URL
                String accessUrl = accessPath+ relativePath.replace("\\", "/");
                imagePaths.add(accessUrl);


                // 保存业务图片关联关系
                PicPathInfo picPathInfo = new PicPathInfo();
                picPathInfo.setBusinessId(businessId);
                picPathInfo.setBusinessType(businessType);
                picPathInfo.setPicPath(accessUrl); //图片路径
                picPathInfo.setCreateBy(createBy);
                picPathInfo.setCreateTime(new Date());
                picPathInfo.setSort(i++);
                picPathInfoService.save(picPathInfo);
            } catch (Exception e) {
                errorMessages.add(file.getOriginalFilename() + "上传失败: " + e.getMessage());
            }
        }

        if (!errorMessages.isEmpty()) {
            result.setMessage(String.join("; ", errorMessages));
        }

        result.setSuccess(true);
        result.setResult(imagePaths);
        return result;
    }
    @GetMapping("/getBusinessImages")
    @ApiOperation(value = "获取业务关联的图片列表",notes="根据业务id-businessId查询图片信息，必传参数businessId")
    public Result<List<PicPathInfo>> getBusinessImages(PicPathInfo queryDTO) {
        Result<List<PicPathInfo>> result = new Result<>();
        try {
            List<PicPathInfo> images = picPathInfoService.queryByBusinessId(queryDTO.getBusinessId(),queryDTO.getBusinessType());
            result.setResult(images);
            result.setSuccess(true);
        } catch (Exception e) {
            result.setSuccess(false);
            result.setMessage("查询失败: " + e.getMessage());
        }
        return result;
    }


    @PostMapping("/batchPreviewImages")
   // @ApiOperation(value="批量预览业务关联的图片", notes="入参必传参数为：businessId 图片所属的业务的表id，businessId 图片所属的业务类型")
    public void batchPreviewImages(@RequestBody PicPathInfo queryDTO,
                                   HttpServletResponse response) {
        try {
            // 获取业务关联的图片列表
            List<PicPathInfo> images = picPathInfoService.queryByBusinessId(queryDTO.getBusinessId(),queryDTO.getBusinessType());
            if (images == null || images.isEmpty()) {
                response.sendError(404, "未找到关联的图片");
                return;
            }
            // 这里可以根据需求实现多种返回方式：
            // 1. 返回第一张图片（示例实现）
            previewSingleImage(images.get(0).getPicPath(), response);

            // 2. 或者返回图片列表的zip压缩包
           //  batchDownloadAsZip(images, response);
        } catch (Exception e) {
            try {
                response.sendError(500, "批量预览图片失败: " + e.getMessage());
            } catch (IOException ex) {
                //log.error("发送错误响应失败", ex);
            }
        }
    }

    @GetMapping("/previewImage")
    @ApiOperation(value = "单张图片预览接口",notes="输入参数图片路径")
    public void previewSingleImage(@RequestParam String imagePath, HttpServletResponse response) {
        if (oConvertUtils.isEmpty(imagePath)) {
            return;
        }
        try {
            // 从访问路径转换为实际存储路径
            String relativePath = imagePath.replace(accessPath, "");
            String realPath = uploadPath + File.separator + relativePath.replace("/", File.separator);

            File file = new File(realPath);
            if (!file.exists()) {
                response.sendError(404, "图片不存在");
                return;
            }

            // 设置响应内容类型
            String contentType = getContentType(imagePath);
            response.setContentType(contentType);

            // 读取文件并写入响应
            try (InputStream in = new FileInputStream(file);
                 OutputStream out = response.getOutputStream()) {
                byte[] buffer = new byte[1024];
                int len;
                while ((len = in.read(buffer)) != -1) {
                    out.write(buffer, 0, len);
                }
                out.flush();
            }
        } catch (Exception e) {
            e.printStackTrace();
        }
    }
    /**
     * 批量下载为ZIP包（可选实现）
     */
    private void batchDownloadAsZip(List<PicPathInfo> images, HttpServletResponse response)
            throws IOException {
        response.setContentType("application/zip");
        response.setHeader("Content-Disposition", "attachment; filename=\"business_images.zip\"");

        try (ZipOutputStream zipOut = new ZipOutputStream(response.getOutputStream())) {
            for (PicPathInfo image : images) {
                String relativePath = image.getPicPath().replace(accessPath, "");
                String realPath = uploadPath + File.separator + relativePath.replace("/", File.separator);
                File file = new File(realPath);

                if (file.exists()) {
                    ZipEntry zipEntry = new ZipEntry(file.getName());
                    zipOut.putNextEntry(zipEntry);

                    try (FileInputStream fis = new FileInputStream(file)) {
                        byte[] buffer = new byte[1024];
                        int len;
                        while ((len = fis.read(buffer)) > 0) {
                            zipOut.write(buffer, 0, len);
                        }
                    }
                    zipOut.closeEntry();
                }
            }
            zipOut.finish();
        }
    }
    private String getContentType(String imagePath) {
        if (imagePath.endsWith(".png")) {
            return "image/png";
        } else if (imagePath.endsWith(".gif")) {
            return "image/gif";
        } else if (imagePath.endsWith(".jpeg") || imagePath.endsWith(".jpg")) {
            return "image/jpeg";
        }
        return "application/octet-stream";
    }
}